package myoa.tool

import myoa.ProCompany
import myoa.ProEmployee
import myoa.ProUser
import myoa.Project
import myoa.Task
import myoa.User
import myoa.domain.RoleName
import org.apache.shiro.SecurityUtils
import org.apache.shiro.crypto.hash.Sha512Hash

class ShiroTool {

    static boolean isRoot() {
        SecurityUtils.subject.principal == 'root'
    }

    static boolean hasOneRoleOf(RoleName... roleNames) {
        boolean re = false
        roleNames.each {
            if (SecurityUtils.subject.hasRole(it.name())) {
                re = true
            }
        }
        return re
    }

    /**
     * default is Sha256Hash. refer to spring/resource.groovy
     * @param open password, like aaaa
     * @return encrypt password, like 81cc5b
     */
    static String encrypt(String pwdOpen) {
        new Sha512Hash(pwdOpen).toHex()
    }


    static boolean byOwner(String params_id, Closure getOwnerId) {
        Long paramsId = Long.valueOf(params_id)
        Long ownerId = getOwnerId(paramsId)
        return SessionTool.loginUser.id == ownerId
    }

    static boolean byOwnerButRoot(String params_id, Closure getOwnerId) {
        return isRoot() || byOwner(params_id, getOwnerId)
    }

    static boolean byShare(String params_id, Closure domainCanRelateToUsers) {
        Long domainId = Long.valueOf(params_id)
        def domain = domainCanRelateToUsers(domainId)
        println domain.class

        Set<User> users
        if (domain instanceof Collection<User>) { // base case
            users = domain
        } else if (domain instanceof Project) {
            users = domain.proUsers*.user
        } else if (domain instanceof ProUser) {
            users = domain.project.proUsers*.user
        } else if (domain instanceof ProCompany) {
            users = domain.project.proUsers*.user
        } else if (domain instanceof Task) {
            users = domain.project.proUsers*.user
        } else if (domain instanceof ProEmployee) {
            users = domain.proCompany.project.proUsers*.user
        }
        assert users != null
        return SessionTool.loginUser.id in users*.id
    }

    static boolean byShareButRoot(String params_id, Closure getShareList) {
        return isRoot() || byShare(params_id, getShareList)
    }
}
